home *** CD-ROM | disk | FTP | other *** search
/ Experimental BBS Explossion 3 / Experimental BBS Explossion III.iso / games / nhak_src.zip / MKOBJ.C < prev    next >
C/C++ Source or Header  |  1993-03-16  |  15KB  |  672 lines

  1. /*    SCCS Id: @(#)mkobj.c    3.0    89/11/08
  2. /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
  3. /* NetHack may be freely redistributed.  See license for details. */
  4.  
  5. #include "hack.h"
  6.  
  7. STATIC_DCL void FDECL(mkbox_cnts,(struct obj *));
  8.  
  9. struct icp {
  10.     int  iprob; /* probability of an item type */
  11.     char ilet;    /* item class */
  12. };
  13.  
  14. #ifdef OVL1
  15.  
  16. const struct icp mkobjprobs[] = {
  17. {10, WEAPON_SYM},
  18. {10, ARMOR_SYM},
  19. {20, FOOD_SYM},
  20. { 8, TOOL_SYM},
  21. { 8, GEM_SYM},
  22. #ifdef SPELLS
  23. {16, POTION_SYM},
  24. {16, SCROLL_SYM},
  25. { 4, SPBOOK_SYM},
  26. #else
  27. {18, POTION_SYM},
  28. {18, SCROLL_SYM},
  29. #endif
  30. { 4, WAND_SYM},
  31. { 3, RING_SYM},
  32. { 1, AMULET_SYM}};
  33.  
  34. const struct icp boxiprobs[] = {
  35. {18, GEM_SYM},
  36. #ifdef SPELLS
  37. {15, FOOD_SYM},
  38. {20, POTION_SYM},
  39. {20, SCROLL_SYM},
  40. {15, SPBOOK_SYM},
  41. #else
  42. {20, FOOD_SYM},
  43. {25, POTION_SYM},
  44. {25, SCROLL_SYM},
  45. #endif
  46. { 6, WAND_SYM},
  47. { 5, RING_SYM},
  48. { 1, AMULET_SYM}};
  49.  
  50. #ifdef REINCARNATION
  51. const struct icp rogueprobs[] = {
  52. {12, WEAPON_SYM},
  53. {12, ARMOR_SYM},
  54. {22, FOOD_SYM},
  55. {22, POTION_SYM},
  56. {22, SCROLL_SYM},
  57. { 5, WAND_SYM},
  58. { 5, RING_SYM}};
  59. #endif
  60.  
  61. const struct icp hellprobs[] = {
  62. {20, WEAPON_SYM},
  63. {20, ARMOR_SYM},
  64. {16, FOOD_SYM},
  65. {12, TOOL_SYM},
  66. {10, GEM_SYM},
  67. { 1, POTION_SYM},
  68. { 1, SCROLL_SYM},
  69. { 8, WAND_SYM},
  70. { 8, RING_SYM},
  71. { 4, AMULET_SYM}};
  72.  
  73. static int NEARDATA mksx=0, NEARDATA mksy=0;
  74.  
  75. struct obj *
  76. mkobj_at(let,x,y, artif)
  77. char let;
  78. int x,y;
  79. boolean artif;
  80. {
  81.     register struct obj *otmp;
  82.  
  83.     mksx = x; mksy = y;
  84.     /* We need to know the X, Y coordinates while creating the object,
  85.      * to insure shop boxes are empty.
  86.      * Yes, this is a horrible kludge...
  87.      */
  88.     otmp = mkobj(let,artif);
  89.     otmp->nobj = fobj;
  90.     fobj = otmp;
  91.     place_object(otmp, x, y);
  92.     mksx = mksy = 0;
  93.     return(otmp);
  94. }
  95.  
  96. struct obj *
  97. mksobj_at(otyp,x,y)
  98. int otyp,x,y;
  99. {
  100.     register struct obj *otmp;
  101.  
  102.     mksx = x; mksy = y;
  103.     otmp = mksobj(otyp,TRUE);
  104.     otmp->nobj = fobj;
  105.     place_object(otmp, x, y);
  106.     mksx = mksy = 0;
  107.     return((fobj = otmp));
  108. }
  109.  
  110. struct obj *
  111. mkobj(let, artif)
  112. char let;
  113. boolean artif;
  114. {
  115.     register int tprob, i, prob = rnd(1000);
  116.  
  117.     if(let == RANDOM_SYM) {
  118.         const struct icp *iprobs =
  119. #ifdef REINCARNATION
  120.                     (dlevel == rogue_level) ?
  121.                     (const struct icp *)rogueprobs :
  122. #endif
  123.                     Inhell ? (const struct icp *)hellprobs :
  124.                     (const struct icp *)mkobjprobs;
  125.  
  126.         for(tprob = rnd(100);
  127.             (tprob -= iprobs->iprob) > 0;
  128.             iprobs++);
  129.         let = iprobs->ilet;
  130.     }
  131.  
  132.     i = bases[letindex(let)];
  133.     while((prob -= objects[i].oc_prob) > 0) i++;
  134.  
  135.     if(objects[i].oc_olet != let || !objects[i].oc_name)
  136.         panic("probtype error, let=%c i=%d", let, i);
  137.  
  138.     return(mksobj(i, artif));
  139. }
  140.  
  141. STATIC_OVL
  142. void
  143. mkbox_cnts(box)
  144. /* Note: does not check to see if it overloaded the box capacity; usually
  145.  * possible only with corpses in ice boxes.
  146.  */
  147. struct obj *box;
  148. {
  149.     register int n;
  150.     register struct obj *otmp;
  151.  
  152.     if(in_shop(mksx, mksy)) return; /* boxes are empty in shops */
  153.  
  154.     switch(box->otyp) {
  155.         case ICE_BOX:         n = 20; break;
  156.         case CHEST:        n = 5; break;
  157.         case LARGE_BOX:        n = 3; break;
  158.         case SACK:
  159.         case BAG_OF_HOLDING:    n = 1; break;
  160.         default:        n = 0; break;
  161.     }
  162.  
  163.     for(n = rn2(n+1); n > 0; n--) {
  164.         if (box->otyp == ICE_BOX) {
  165.         otmp = mksobj(CORPSE, TRUE);
  166.         /* Note: setting age to 0 is correct.  Age has a different
  167.          * from usual meaning for objects stored in ice boxes. -KAA
  168.          */
  169.         otmp->age = 0;
  170.         } else {
  171.         register int tprob;
  172.         const struct icp *iprobs = boxiprobs;
  173.  
  174.         for(tprob = rnd(100);
  175.             (tprob -= iprobs->iprob) > 0;
  176.             iprobs++);
  177.         otmp = mkobj(iprobs->ilet, TRUE);
  178.         }
  179.         if (otmp) {
  180.         otmp->cobj = box;
  181.         otmp->nobj = fcobj;
  182.         fcobj = otmp;
  183.         /* inc_cwt(box, otmp); --done by weight() */
  184.         }
  185.     }
  186.     return;
  187. }
  188.  
  189. int
  190. rndmonnum() {    /* select a random, common monster type */
  191.  
  192.     register struct permonst *ptr;
  193.     register int    i;
  194.  
  195.     /* Plan A: get a level-appropriate common monster */
  196.     ptr = rndmonst();
  197.     if (ptr) return(monsndx(ptr));
  198.  
  199.     /* Plan B: get any common monster */
  200.     do {
  201.         ptr = &mons[(i = rn2(NUMMONS))];
  202.     } while((ptr->geno & G_NOGEN) || (!Inhell && (ptr->geno & G_HELL)));
  203.  
  204.     return(i);
  205. }
  206.  
  207. #endif /* OVL1 */
  208. #ifdef OVLB
  209. const char dknowns[] = { WAND_SYM, RING_SYM, POTION_SYM, SCROLL_SYM, GEM_SYM,
  210. #ifdef SPELLS
  211. SPBOOK_SYM,
  212. #endif
  213. WEAPON_SYM, 0};
  214.  
  215. /*ARGSUSED*/
  216. struct obj *
  217. mksobj(otyp, artif)
  218. int otyp;
  219. boolean artif;
  220. {
  221.     int tryct;
  222.     struct obj *otmp;
  223.     char let = objects[otyp].oc_olet;
  224.  
  225.     otmp = newobj(0);
  226.     *otmp = zeroobj;
  227.     otmp->age = monstermoves;
  228.     otmp->o_id = flags.ident++;
  229.     otmp->quan = 1;
  230.     otmp->olet = let;
  231.     otmp->otyp = otyp;
  232.     otmp->dknown = index(dknowns, let) ? 0 : 1;
  233.     if (!objects[otmp->otyp].oc_uses_known)
  234.         otmp->known = 1;
  235.     switch(let) {
  236.     case WEAPON_SYM:
  237.         otmp->quan = (otmp->otyp <= SHURIKEN) ? rn1(6,6) : 1;
  238.         if(!rn2(11)) {
  239.             otmp->spe = rne(3);
  240.             otmp->blessed = rn2(2);
  241.         } else if(!rn2(10)) {
  242.             curse(otmp);
  243.             otmp->spe = -rne(3);
  244.         } else    blessorcurse(otmp, 10);
  245.  
  246. #ifdef NAMED_ITEMS
  247.         if(artif && !rn2(20)) mkartifact(&otmp);
  248. #endif
  249.         break;
  250.     case FOOD_SYM:
  251.         otmp->oeaten = 0;
  252.         if(otmp->otyp == CORPSE) {
  253.             /* overridden by mkcorpstat() */
  254.             do otmp->corpsenm = rndmonnum();
  255.             while (mons[otmp->corpsenm].geno & G_NOCORPSE);
  256.             break;
  257.         } else if(otmp->otyp == EGG) {
  258.             if(!rn2(3)) {        /* "live" eggs */
  259.             register struct permonst *ptr;
  260.             for(tryct = 0;
  261.                 (!(ptr = rndmonst()) ||
  262.                 (!lays_eggs(ptr) && ptr != &mons[PM_KILLER_BEE])) &&
  263.                 tryct < 100;
  264.                 tryct++);
  265.             if(tryct < 100)    otmp->corpsenm = monsndx(ptr);
  266.             else        otmp->corpsenm = -1; /* empty */
  267.             } else        otmp->corpsenm = -1; /* empty */
  268.         } else if(otmp->otyp == TIN) {
  269.             if(!rn2(6)) {
  270.             otmp->spe = 1;        /* spinach */
  271.             otmp->corpsenm = -1;
  272.             } else do {
  273.             otmp->corpsenm = rndmonnum();
  274.             } while (mons[otmp->corpsenm].geno & G_NOCORPSE);
  275.             blessorcurse(otmp, 10);
  276.         }
  277. #ifdef TUTTI_FRUTTI
  278.         else if (otmp->otyp == SLIME_MOLD)
  279.             otmp->spe = current_fruit;
  280. #endif
  281.         /* fall into next case */
  282.     case GEM_SYM:
  283.         if (otmp->otyp == LOADSTONE) curse(otmp);
  284.         else if (otmp->otyp == ROCK) otmp->quan = rn1(6,6);
  285.         else if (otmp->otyp != LUCKSTONE && !rn2(6)) otmp->quan = 2;
  286.         else otmp->quan = 1;
  287.         break;
  288.     case TOOL_SYM:
  289.         switch(otmp->otyp) {
  290.         case LAMP:        otmp->spe = rnd(10);
  291.                     blessorcurse(otmp, 5);
  292.                     break;
  293.         case MAGIC_LAMP:    otmp->spe = 1;
  294.                     otmp->recharged = 0;
  295.                     blessorcurse(otmp, 2);
  296.                     break;
  297.         case KEY:        /* key # index */
  298.         case SKELETON_KEY:    otmp->spe = rn2(N_LOX);
  299.                     break;
  300.         case CHEST:        /* lock # index */
  301.         case LARGE_BOX:        otmp->spe = rn2(N_LOX);
  302.                     otmp->olocked = !!(rn2(5));
  303.                     otmp->otrapped = !(rn2(10));
  304.         case ICE_BOX:
  305.         case SACK:
  306.         case BAG_OF_HOLDING:    mkbox_cnts(otmp);
  307.                     break;
  308.         case MAGIC_MARKER:    otmp->spe = rn1(70,30);
  309.                     break;
  310.         case CRYSTAL_BALL:    otmp->spe = rnd(5);
  311.                     blessorcurse(otmp, 2);
  312.                     break;
  313.         case BAG_OF_TRICKS:    otmp->spe = rnd(20);
  314.                     break;
  315.         case FIGURINE:    {    int tryct2 = 0;
  316.                     do
  317.                         otmp->corpsenm = rndmonnum();
  318.                     while(is_human(&mons[otmp->corpsenm])
  319.                         && tryct2++ < 30);
  320.                     blessorcurse(otmp, 4);
  321.                     break;
  322.                 }
  323. #ifdef MUSIC
  324.         case MAGIC_FLUTE:
  325.         case MAGIC_HARP:
  326.         case FROST_HORN:
  327.         case FIRE_HORN:
  328.         case DRUM_OF_EARTHQUAKE:
  329.                     otmp->spe = rn1(5,4);
  330.                     break;
  331. #endif /* MUSIC /**/
  332.         }
  333.         break;
  334.     case AMULET_SYM:
  335.         if(rn2(10) && (otmp->otyp == AMULET_OF_STRANGULATION ||
  336.            otmp->otyp == AMULET_OF_CHANGE ||
  337.            otmp->otyp == AMULET_OF_RESTFUL_SLEEP)) {
  338.             curse(otmp);
  339.         } else    blessorcurse(otmp, 10);
  340.     case VENOM_SYM:
  341.     case CHAIN_SYM:
  342.     case BALL_SYM:
  343.         break;
  344.     case POTION_SYM:
  345.     case SCROLL_SYM:
  346. #ifdef MAIL
  347.         if (otmp->otyp != SCR_MAIL)
  348. #endif
  349.             blessorcurse(otmp, 4);
  350.         break;
  351. #ifdef SPELLS
  352.     case SPBOOK_SYM:
  353.         blessorcurse(otmp, 17);
  354.         break;
  355. #endif
  356.     case ARMOR_SYM:
  357.         if(rn2(10) && (otmp->otyp == FUMBLE_BOOTS ||
  358.            otmp->otyp == LEVITATION_BOOTS ||
  359.            otmp->otyp == HELM_OF_OPPOSITE_ALIGNMENT ||
  360.            otmp->otyp == GAUNTLETS_OF_FUMBLING ||
  361.            !rn2(11))) {
  362.             curse(otmp);
  363.             otmp->spe = -rne(3);
  364.         } else if(!rn2(10)) {
  365.             otmp->spe = rne(3);
  366.             otmp->blessed = rn2(2);
  367.         } else    blessorcurse(otmp, 10);
  368.         if(otmp->otyp == DRAGON_SCALE_MAIL)
  369.             otmp->corpsenm = PM_GRAY_DRAGON +
  370.                 rn2(PM_YELLOW_DRAGON-PM_GRAY_DRAGON+1);
  371.         break;
  372.     case WAND_SYM:
  373. #ifdef HARD
  374.         if(otmp->otyp == WAN_WISHING) otmp->spe = rnd(3); else
  375. #else        
  376.         if(otmp->otyp == WAN_WISHING) otmp->spe = 3; else
  377. #endif        
  378.         otmp->spe = rn1(5,
  379.             (objects[otmp->otyp].bits & NODIR) ? 11 : 4);
  380.         blessorcurse(otmp, 17);
  381.         otmp->recharged = 0; /* used to control recharging */
  382.         break;
  383.     case RING_SYM:
  384.         if(objects[otmp->otyp].oc_charged) {
  385.             blessorcurse(otmp, 3);
  386.             if(rn2(10)) {
  387.             if(rn2(10) && bcsign(otmp))
  388.                 otmp->spe = bcsign(otmp) * rne(3);
  389.             else otmp->spe = rn2(2) ? rne(3) : -rne(3);
  390.             }
  391.             if (otmp->spe < 0 && rn2(5)) curse(otmp);
  392.         } else if(rn2(10) && (otmp->otyp == RIN_TELEPORTATION ||
  393. #ifdef POLYSELF
  394.               otmp->otyp == RIN_POLYMORPH ||
  395. #endif
  396.               otmp->otyp == RIN_AGGRAVATE_MONSTER ||
  397.               otmp->otyp == RIN_HUNGER || !rn2(9))) {
  398.             curse(otmp);
  399.         }
  400.         break;
  401.     case ROCK_SYM:
  402.         switch (otmp->otyp) {
  403.             case STATUE:
  404.             /* contains book? */
  405.             otmp->spe = (rn2(dlevel/2 + 10) > 10);
  406.             /* overridden by mkcorpstat() */
  407.             otmp->corpsenm = rndmonnum();
  408.         }
  409.         break;
  410.     default:
  411.         impossible("impossible mkobj %d, sym '%c'.", otmp->otyp, let);
  412.         return (struct obj *)0;
  413.     }
  414.     otmp->owt = weight(otmp);
  415.     return(otmp);
  416. }
  417.  
  418. void
  419. bless(otmp)
  420. register struct obj *otmp;
  421. {
  422.     otmp->cursed = 0;
  423.     otmp->blessed = 1;
  424.     if (otmp->otyp == LUCKSTONE) {
  425.         if (stone_luck(TRUE) >= 0) u.moreluck = LUCKADD;
  426.         else u.moreluck = -LUCKADD;
  427.     }
  428.     return;
  429. }
  430.  
  431. void
  432. curse(otmp)
  433. register struct obj *otmp;
  434. {
  435.     otmp->blessed = 0;
  436.     otmp->cursed = 1;
  437.     if (otmp->otyp == LUCKSTONE) {
  438.         if (stone_luck(TRUE) >= 0) u.moreluck = LUCKADD;
  439.         else u.moreluck = -LUCKADD;
  440.     }
  441.     return;
  442. }
  443.  
  444. #endif /* OVLB */
  445. #ifdef OVL1
  446. void
  447. blessorcurse(otmp, chance)
  448. register struct obj *otmp;
  449. register int chance;
  450. {
  451.     if(otmp->blessed || otmp->cursed) return;
  452.  
  453.     if(!rn2(chance))
  454.         if(!rn2(2) || Inhell) { /* in hell, don't usually bless items */
  455.         curse(otmp);
  456.         } else {
  457.         bless(otmp);
  458.         }
  459.     return;
  460. }
  461.  
  462. #endif /* OVL1 */
  463. #ifdef OVLB
  464. int
  465. bcsign(otmp)
  466. register struct obj *otmp;
  467. {
  468.     return(!!otmp->blessed - !!otmp->cursed);
  469. }
  470.  
  471. int
  472. letter(c)
  473. int c;
  474. {
  475.     return(('@' <= c && c <= 'Z') || ('a' <= c && c <= 'z'));
  476. }
  477.  
  478. #endif /* OVLB */
  479. #ifdef OVL0
  480.  
  481. int
  482. weight(obj)
  483. register struct obj *obj;
  484. {
  485.     register int wt = objects[obj->otyp].oc_weight;
  486.  
  487.     if (Is_container(obj)) {
  488.         struct obj *contents;
  489.         obj->owt = wt;
  490.         for(contents=fcobj; contents; contents=contents->nobj) {
  491.             if (contents->cobj == obj)
  492.                 inc_cwt(obj, contents);
  493.         }
  494.         return obj->owt;
  495.     }
  496.     if (obj->otyp == CORPSE && obj->corpsenm > -1)
  497.         return obj->quan * mons[obj->corpsenm].cwt;
  498.     else if (obj->otyp == STATUE && obj->corpsenm > -1)
  499.         return obj->quan * (mons[obj->corpsenm].cwt * 3 / 2);
  500.     return(wt ? wt*obj->quan : (obj->quan + 1)>>1);
  501. }
  502.  
  503. #endif /* OVL0 */
  504. #ifdef OVLB
  505.  
  506. void
  507. mkgold(num,x,y)
  508. long num;
  509. int x, y;
  510. {
  511.     register struct gold *gold;
  512.     register long amount = (num ? num : 1 + (rnd(dlevel+2) * rnd(30)));
  513.  
  514.     if(levl[x][y].gmask) {
  515.         gold = g_at(x,y);
  516.         gold->amount += amount;
  517.     } else {
  518.         gold = newgold();
  519.         gold->ngold = fgold;
  520.         gold->gx = x;
  521.         gold->gy = y;
  522.         gold->amount = amount;
  523.         fgold = gold;
  524.         levl[x][y].gmask = 1;
  525.         /* do sth with display? */
  526.     }
  527.     return;
  528. }
  529.  
  530. #endif /* OVLB */
  531. #ifdef OVL1
  532. struct obj *
  533. mkcorpstat(objtype, ptr, x, y)
  534. int objtype;    /* CORPSE or STATUE */
  535. register struct permonst *ptr;
  536. int x, y;
  537. {
  538.     register struct obj *otmp;
  539.  
  540.     if(objtype != CORPSE && objtype != STATUE)
  541.         impossible("making corpstat type %d", objtype);
  542.     otmp = mksobj_at(objtype, x, y);
  543.     if(otmp)  {
  544.         if(ptr)    otmp->corpsenm = monsndx(ptr);
  545.         else    otmp->corpsenm = rndmonnum();
  546.         otmp->owt = weight(otmp);
  547.     }
  548.     return(otmp);
  549. }
  550.  
  551. #endif /* OVL1 */
  552. #ifdef OVLB
  553. struct obj *
  554. mk_tt_object(objtype, x, y)
  555. int objtype; /* CORPSE or STATUE */
  556. register int x, y;
  557. {
  558.     register struct obj *otmp;
  559.  
  560.     if(otmp = mksobj_at(objtype,x,y)) {
  561.         if((otmp = tt_oname(otmp)) && objtype == STATUE)
  562.             /* player statues never contain books */
  563.             otmp->spe = 0;
  564.     }
  565.     return(otmp);
  566. }
  567.  
  568. struct obj *
  569. mk_named_object(objtype, ptr, x, y, nm, lth)
  570. int objtype; /* CORPSE or STATUE */
  571. register struct permonst *ptr;
  572. int x, y;
  573. char * nm;
  574. register int lth;
  575. {
  576.     struct obj *otmp;
  577.  
  578.     otmp = mkcorpstat(objtype,ptr,x,y);
  579.     if (lth > 0) {
  580.         /* Note: oname() is safe since otmp is first in both chains */
  581.         otmp = oname(otmp, nm, FALSE);
  582.         fobj = otmp;
  583.         level.objects[x][y] = otmp;
  584.     }
  585.     return(otmp);
  586. }
  587.  
  588. boolean
  589. is_flammable(otmp)
  590. register struct obj *otmp;
  591. {
  592.     int otyp = otmp->otyp;
  593.  
  594.     if (otyp == DRAGON_SCALE_MAIL && otmp->corpsenm == PM_RED_DRAGON)
  595.         return FALSE;
  596.     return((objects[otyp].oc_material == WOOD ||
  597.             objects[otyp].oc_material == 0));
  598.  
  599. }
  600.  
  601. #ifdef STUPID_CPP
  602. boolean
  603. is_rustprone(otmp)
  604. register struct obj *otmp;
  605. {
  606.     return(objects[otmp->otyp].oc_material == METAL);
  607. }
  608.  
  609. boolean
  610. is_corrodeable(otmp)
  611. register struct obj *otmp;
  612. {
  613.     return(objects[otmp->otyp].oc_material == COPPER);
  614. }
  615.  
  616. boolean
  617. OBJ_AT(x, y)
  618. int x, y;
  619. {
  620.     return(level.objects[x][y] != (struct obj *)0);
  621. }
  622. #endif
  623.  
  624. #endif /* OVLB */
  625. #ifdef OVL1
  626.  
  627. /*
  628.  * These routines maintain the single-linked lists headed in level.objects[][]
  629.  * and threaded through the nexthere fields in the object-instance structure.
  630.  */
  631.  
  632. void
  633. place_object(otmp, x, y)
  634. /* put an object on top of the pile at the given location */
  635. register struct obj *otmp;
  636. int x, y;
  637. {
  638.     otmp->nexthere = level.objects[x][y];
  639.     level.objects[x][y] = otmp;
  640.  
  641.     /* set the new object's location */
  642.     otmp->ox = x;
  643.     otmp->oy = y;
  644. }
  645.  
  646. #endif /* OVL1 */
  647. #ifdef OVLB
  648. void
  649. remove_object(otmp)
  650. register struct obj *otmp;
  651. {
  652.     register struct obj *odel;
  653.  
  654.     if (otmp == level.objects[otmp->ox][otmp->oy])
  655.     level.objects[otmp->ox][otmp->oy] = otmp->nexthere;
  656.     else
  657.     for (odel = level.objects[otmp->ox][otmp->oy];
  658.                             odel; odel = odel->nexthere)
  659.         if (odel->nexthere == otmp)
  660.         odel->nexthere = otmp->nexthere;
  661. }
  662.  
  663. void move_object(otmp, x, y)
  664. register struct obj *otmp;
  665. int x, y;
  666. {
  667.     remove_object(otmp);
  668.     place_object(otmp, x, y);
  669. }
  670.  
  671. #endif /* OVLB */
  672.